/*
 * Basic no frills app which integrates the ZBar barcode scanner with
 * the camera.
 * 
 * Created by lisah0 on 2012-02-24
 */
package com.xindaoapp.henghua.zbar;

import java.io.IOException;

import net.sourceforge.zbar.Config;
import net.sourceforge.zbar.Image;
import net.sourceforge.zbar.ImageScanner;
import net.sourceforge.zbar.Symbol;
import net.sourceforge.zbar.SymbolSet;
import android.app.Activity;
import android.content.Intent;
import android.content.res.AssetFileDescriptor;
import android.hardware.Camera;
import android.hardware.Camera.AutoFocusCallback;
import android.hardware.Camera.PreviewCallback;
import android.hardware.Camera.Size;
import android.media.AudioManager;
import android.media.MediaPlayer;
import android.media.MediaPlayer.OnCompletionListener;
import android.os.Bundle;
import android.os.Handler;
import android.os.Vibrator;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.Window;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.FrameLayout;
import android.widget.TextView;
import android.widget.Toast;

import com.xindaoapp.henghua.R;
import com.xindaoapp.henghua.activity.AddLabel;
import com.xindaoapp.henghua.application.XinDaoApplication;
import com.xindaoapp.henghua.entry.PropertyGatherInfo;

public class CameraTestActivity extends Activity {

	private static final float BEEP_VOLUME = 0.10f;
	private static final long VIBRATE_DURATION = 200L;

	private Camera mCamera;
	private CameraPreview mPreview;
	private Handler autoFocusHandler;
	private MediaPlayer mediaPlayer;
	private boolean playBeep = true;

	ImageScanner scanner;

	private boolean previewing = true;

	/** 获取设备相关所有信息*/
	private PropertyGatherInfo info = null;

	private Button cancelScanButton;

	private TextView tv_prompt;
	private TextView tv_promptError;

	static {
		System.loadLibrary("iconv");
	}

	private Button btnRescan;

	boolean canRescan = false;

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		this.requestWindowFeature(Window.FEATURE_NO_TITLE);
		this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
				WindowManager.LayoutParams.FLAG_FULLSCREEN);
		setContentView(R.layout.zbar_capture);

		autoFocusHandler = new Handler();
		mCamera = getCameraInstance();

		if (null == mCamera) {
			Toast.makeText(this, "照相机发生故障，请重试", Toast.LENGTH_SHORT).show();
			return;
		}

		/* Instance barcode scanner */
		scanner = new ImageScanner();
		scanner.setConfig(0, Config.X_DENSITY, 2);
		scanner.setConfig(0, Config.Y_DENSITY, 2);

		mPreview = new CameraPreview(this, mCamera, previewCb, autoFocusCB);
		FrameLayout preview = (FrameLayout) findViewById(R.id.cameraPreview);
		preview.addView(mPreview);

		mCamera.setPreviewCallback(previewCb);
		mCamera.startPreview();
		previewing = true;
		mCamera.autoFocus(autoFocusCB);

		// 初始化声音和震动
		AudioManager audioService = (AudioManager) getSystemService(AUDIO_SERVICE);
		// 如果手机是震动模式就震动
		if (audioService.getRingerMode() != AudioManager.RINGER_MODE_NORMAL) {
			playBeep = false;
		}
		// 初始化声音
		initBeepSound();

		info = (PropertyGatherInfo) getIntent().getSerializableExtra("info");

		tv_prompt = (TextView) findViewById(R.id.preview_tv_scan);
		tv_promptError = (TextView) findViewById(R.id.preview_tv_scan_error);

		cancelScanButton = (Button) findViewById(R.id.preview_btn_cancle);

		// quit the scan view
		cancelScanButton.setOnClickListener(new OnClickListener() {

			@Override
			public void onClick(View v) {
				CameraTestActivity.this.finish();
			}
		});

		// 重拍
//		btnRescan = (Button) findViewById(R.id.btnRescan);
//		btnRescan.setOnClickListener(new OnClickListener() {
//
//			@Override
//			public void onClick(View v) {
//
//				if (canRescan) {
//					previewing = true;
//					mCamera.setPreviewCallback(previewCb);
//					mCamera.startPreview();
//				}
//			}
//		});

	}

	@Override
	public void onPause() {
		super.onPause();
		releaseCamera();
	}

	/** A safe way to get an instance of the Camera object. */
	public static Camera getCameraInstance() {
		Camera c = null;
		try {
			c = Camera.open();
		} catch (Exception e) {}
		return c;
	}

	private void releaseCamera() {
		if (mCamera != null) {
			previewing = false;
			mCamera.setPreviewCallback(null);
			mCamera.release();
			mCamera = null;
		}
	}

	private final Runnable doAutoFocus = new Runnable() {
		@Override
		public void run() {
			if (previewing)
				mCamera.autoFocus(autoFocusCB);
		}
	};

	PreviewCallback previewCb = new PreviewCallback() {
		@Override
		public void onPreviewFrame(byte[] data, Camera camera) {
			Camera.Parameters parameters = camera.getParameters();
			Size size = parameters.getPreviewSize();

			Image barcode = new Image(size.width, size.height, "Y800");
			barcode.setData(data);

			int result = scanner.scanImage(barcode);

			if (result != 0) {
				previewing = false;
				mCamera.setPreviewCallback(null);
				mCamera.stopPreview();

				SymbolSet syms = scanner.getResults();

				playBeepSoundAndVibrate();// 播放声音和振动代表成功获取二维码

				for (Symbol sym : syms) {

					final String resultString = sym.getData();

					System.out.println("Result:" + resultString);
					XinDaoApplication.getHandler().post(new Runnable() {

						@Override
						public void run() {
//							Toast.makeText(CameraTestActivity.this, resultString, Toast.LENGTH_SHORT).show();
						}
					});
					boolean isRight = isRigthCode(resultString);
					
					if (isRight) {

						Intent intent = new Intent(CameraTestActivity.this, AddLabel.class);
						Bundle mBundle = new Bundle();
						mBundle.putSerializable("info", info);
						intent.putExtras(mBundle);
						intent.putExtra("scanCode", resultString);
						startActivity(intent);

						canRescan = false;
						finish();
						// Toast.makeText(CaptureActivity.this, "合法标签",
						// Toast.LENGTH_SHORT).show();
						break;
					} else {
						XinDaoApplication.getHandler().post(new Runnable() {

							@Override
							public void run() {
//								Toast.makeText(CameraTestActivity.this, "非法标签", Toast.LENGTH_SHORT).show();
							}
						});

						tv_prompt.setVisibility(View.GONE);
						tv_promptError.setVisibility(View.VISIBLE);
						CharSequence text = getString(R.string.scan_alert_error, resultString);
						tv_promptError.setText(text);
						canRescan = true;
						break;
					}
					
				}

			}
		}
	};

	private boolean isRigthCode(String code) {

		boolean isRight = true;

		// 判断是否为已贴标签
		boolean isTie = XinDaoApplication.get().getDBHelper().isExistLabel(code);

		if (isTie) {
			return false;
		}

		// 判断是否合法
		boolean isHf = XinDaoApplication.get().getUpdateDataChanged().isExistLabel(code);
		if (!isHf) {
			return false;
		}

		return isRight;
	}

	// Mimic continuous auto-focusing
	AutoFocusCallback autoFocusCB = new AutoFocusCallback() {
		@Override
		public void onAutoFocus(boolean success, Camera camera) {
			autoFocusHandler.postDelayed(doAutoFocus, 1000);
		}
	};

	/**
	 * 初始化声音
	 */
	private void initBeepSound() {
		if (playBeep && mediaPlayer == null) {
			setVolumeControlStream(AudioManager.STREAM_MUSIC);
			mediaPlayer = new MediaPlayer();
			mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
			mediaPlayer.setOnCompletionListener(beepListener);
			AssetFileDescriptor file = getResources().openRawResourceFd(R.raw.beep);
			try {
				mediaPlayer.setDataSource(file.getFileDescriptor(), file.getStartOffset(), file.getLength());
				file.close();
				mediaPlayer.setVolume(BEEP_VOLUME, BEEP_VOLUME);
				mediaPlayer.prepare();
			} catch (IOException e) {
				mediaPlayer = null;
			}
		}
	}

	/**
	 * 播放声音和震动
	 */
	private void playBeepSoundAndVibrate() {
		if (playBeep && mediaPlayer != null) {
			mediaPlayer.start();
		}
		// 打开震动
		Vibrator vibrator = (Vibrator) getSystemService(VIBRATOR_SERVICE);
		vibrator.vibrate(VIBRATE_DURATION);
	}

	private final OnCompletionListener beepListener = new OnCompletionListener() {
		@Override
		public void onCompletion(MediaPlayer mediaPlayer) {
			mediaPlayer.seekTo(0);
		}
	};
}
